﻿namespace AB.ServiceDirectory.Dao
{
    using System.Linq;
    using Entities;
    using Commons.DataFilters;

    /// <summary>
    /// class AOrganisationDao
    /// </summary>
    public sealed class AOrganizationDao
    {
        /// <summary>
        /// Data Context
        /// </summary>
        private static readonly ServicesDirectoryDataContext DataContext = DB.Context;

        /// <summary>
        /// Prevents a default instance of the <see cref="AOrganizationDao"/> class from being created.
        /// </summary>
        private AOrganizationDao(){}

        /// <summary>
        /// Updates the status.
        /// </summary>
        /// <param name="organizationId">The organistion id.</param>
        /// <param name="active">if set to <c>true</c> [active].</param>
        /// <returns>true/false result</returns>
        public static bool UpdateStatus(int organizationId,bool active)
        {

            bool flag = false;
            var query = DataContext.Organizations.FirstOrDefault(c => c.OrganizationId == organizationId);
            if (query != null)
            {
                query.IsActive = active;
                DataContext.SubmitChanges();
                flag = true;
            }
            return flag;
        }

        /// <summary>
        /// Gets the list organisation count.
        /// </summary>
        /// <param name="filter">The filter.</param>
        /// <returns></returns>
        public  static int GetListOrganizationCount(AOrganizationFilter filter)
        {
            var query = from o in DataContext.Organizations select o;
            return GetListFilter(query, filter).Count();

        }

        /// <summary>
        /// Gets the list organisation id.
        /// </summary>
        /// <param name="id">The id.</param>
        /// <returns></returns>
        public static Organization GetOrganizationById(int id)
        {
            var query = DataContext.Organizations.FirstOrDefault(o => o.OrganizationId == id);
            return query;
        }

        /// <summary>
        /// Gets the list organisation.
        /// </summary>
        /// <param name="filter">A organisation filter.</param>
        /// <param name="softType">Type of the soft.</param>
        /// <param name="startRowIndex">Start index of the row.</param>
        /// <param name="maxRows">The max rows.</param>
        /// <returns></returns>
        public static IQueryable<Organization> GetListOrganization(AOrganizationFilter filter,string softType,int startRowIndex,int maxRows)
        {
            IQueryable<Organization> query = from c in DataContext.Organizations select c;

            // 1.Filter Method
            if (filter != null)
            {
                query = GetListFilter(query, filter);
            }
            // 2.Sorting Column
            query = GetListSort(query, softType);

            // 3.Pagging
            query=query.Skip(startRowIndex).Take(maxRows);
            return query;

        }

        /// <summary>
        /// Gets the list sort.
        /// </summary>
        /// <param name="query">The query.</param>
        /// <param name="softType">Type of the soft.</param>
        /// <returns></returns>
        private static IQueryable<Organization> GetListSort(IQueryable<Organization> query, string softType)
        {
            bool desc = false;
            if(!string.IsNullOrEmpty(softType))
            {
                string[] value = softType.Split(' ');
                softType = value[0];
                if(value.Length>1)
                {
                    desc = (value[1] == "DESC");
                }
                switch (softType)
                {
                    case "OrganizationName":
                        query = desc
                                    ? query.OrderByDescending(o => o.OrganizationName)
                                    : query.OrderBy(o => o.OrganizationName);
                        break;
                    case "AddressLine":
                        query = desc
                                    ? query.OrderByDescending(o => o.Address.AddressLine)
                                    : query.OrderBy(o => o.Address.AddressLine);
                        break;

                    case "PostCode":
                        query = desc
                                    ? query.OrderByDescending(o => o.Address.Postcode)
                                    : query.OrderBy(o => o.Address.Postcode);
                        break;

                    case "Contact":
                        query = desc
                                    ? query.OrderByDescending(o => o.Contact.ContactType.ContactTypeName)
                                    : query.OrderBy(o => o.Contact.ContactType.ContactTypeName);
                        break;
                    case "IsActive":
                        query = desc
                                    ? query.OrderByDescending(o => o.IsActive)
                                    : query.OrderBy(o => o.IsActive);
                        break;

                    default:
                        query = desc
                                    ? query.OrderByDescending(o => o.OrganizationId)
                                    : query.OrderBy(o => o.OrganizationId);
                        break;
                        
                    
                }

            }
            return query;

        }

        /// <summary>
        /// Gets the list filter.
        /// </summary>
        /// <param name="query">The query.</param>
        /// <param name="aOrganisationFilter">A organisation filter.</param>
        /// <returns></returns>
        private static IQueryable<Organization> GetListFilter(IQueryable<Organization> query, AOrganizationFilter aOrganisationFilter)
        {
           
            if(!aOrganisationFilter.IsActive)
            {
                query = query.Where(c => c.IsActive);
            }

            if (aOrganisationFilter.Letters != null)
            {
                query = query.Where(p => aOrganisationFilter.Letters.Contains(p.OrganizationName[0].ToString()));
            }

            return query;
        }

    }
}